#pragma once
#include "Integer.h"

class Residue
{
private:
	Integer num;
	Integer mod;
public:
	Residue(): num(0), mod(0) {}
	Residue(const Integer &n): num(n), mod(0) {}
	Residue(const unsigned &n): num(n), mod(0) {}
	Residue(const Integer &n, const Integer &mod);
public:
	const Integer& Value() const;
	const Integer& Modulus() const;
	std::string str() const;
	friend std::ostream& operator<<(std::ostream &out, const Residue &n);
	friend bool IsSameSystem(const Residue &m, const Residue &n);
	friend bool operator==(const Residue &lhs, const Residue &rhs);
	friend bool operator!=(const Residue &lhs, const Residue &rhs);
	friend bool operator<(const Residue &lhs, const Residue &rhs);
	friend bool operator<=(const Residue &lhs, const Residue &rhs);
	friend bool operator>(const Residue &lhs, const Residue &rhs);
	friend bool operator>=(const Residue &lhs, const Residue &rhs);
	Residue operator-() const;
	friend Residue operator+(const Residue &lhs, const Residue &rhs);
	Residue& operator+=(const Residue &addend);
	Residue& operator++();
	Residue operator++(int);
	friend Residue operator-(const Residue &lhs, const Residue &rhs);
	Residue& operator-=(const Residue &subtrahend);
	Residue& operator--();
	Residue operator--(int);
	friend Residue operator*(const Residue &lhs, const Residue &rhs);
	Residue& operator*=(const Residue &factor);
	friend Residue Square(const Residue &n);
};

